home *** CD-ROM | disk | FTP | other *** search
/ ADA Programming Guide / ADA Programming Guide.iso / ada_gwu / edit.c < prev    next >
Encoding:
C/C++ Source or Header  |  1996-01-30  |  23.7 KB  |  823 lines

  1. /*
  2.     GWAda Development Environment for 386/486 PCs   
  3.     Copyright (C) 1993, Arthur Vargas Lopes  & Michael Bliss Feldman
  4.                         vlopes@vortex.ufrgs.br mfeldman@seas.gwu.edu
  5.  
  6.     This program is free software; you can redistribute it and/or modify
  7.     it under the terms of the GNU General Public License as published by
  8.     the Free Software Foundation; version 2 of the License.    
  9.  
  10.  
  11.     This program is distributed in the hope that it will be useful,
  12.     but WITHOUT ANY WARRANTY; without even the implied warranty of
  13.     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  14.     GNU General Public License for more details.
  15.  
  16.     You should have received a copy of the GNU General Public License
  17.     along with this program; if not, write to the Free Software
  18.     Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  19. */
  20.  
  21. /* edit.c */
  22.  
  23. #include "externs.h"
  24.  
  25.  
  26. int AVL_COL()
  27. {
  28.     AVL_EDIT_WINDOW_PTR w;
  29.     int i, j = 0, n, n2 = 0;
  30.     char *t, line [30];
  31.     w = &avl_windows[avl_window];
  32.     t = w -> current_line -> line;
  33.     n = strlen(t);
  34.     for(i = 0; i <= w -> txt_col; ++i)  {
  35.         if (*(t + i) == '\t' && i != w -> txt_col)  {
  36.             for (n2= 0; !(((j + 1) % w -> tabsize) == 0); ++n2)    
  37.                 j++;
  38.             j++;
  39.             }
  40.         else 
  41.             j++;
  42.         }
  43.     return j;
  44. }
  45.  
  46.  
  47.  
  48. void AVL_JOIN_RIGHT() /* Join current line with next */
  49. {
  50.     AVL_EDIT_WINDOW_PTR w;
  51.     AVL_LINE_PTR temp, temp2;
  52.     struct rccoord old;
  53.     int pos, pos2;
  54.     w = &avl_windows[avl_window];
  55.     if (w -> current_line -> next != w -> head)  {
  56.         pos2 = w -> txt_col;
  57.         if ((strlen(w -> current_line -> line) + strlen(w -> current_line -> next -> line)) >= AVL_MAX_LINEL)  {
  58.             AVL_ERROR("Lines are too long. Can't perform join!");
  59.             return;
  60.             }
  61.         if (w -> scr_row < (w -> r2 - w -> r1 + 1))  {
  62.             old = _settextposition(w -> scr_row+1,w -> scr_col);
  63.             AVL_DELETE_LINE();
  64.             }
  65.         else
  66.             old = _settextposition(w -> scr_row,w -> scr_col);
  67.         
  68.         temp = w -> current_line -> next;
  69.         strcat(w -> current_line -> line,temp -> line);
  70.         w -> current_line -> next = temp -> next;
  71.         temp -> next -> previous = w -> current_line;
  72.         AVL_MAKE_NUMBER();
  73.         free(temp);
  74.         pos = w -> scr_row;
  75.         temp = temp2 = w -> current_line;
  76.         while (++pos != (w -> r2 - w -> r1 + 1) && temp -> next != w -> head)    {
  77.             temp = temp -> next;
  78.             }
  79.         if (pos == (w -> r2 - w -> r1 + 1) && temp != w -> head)  {
  80.             w -> current_line = temp;
  81.             w -> scr_row = w -> r2 - w -> r1 + 1;
  82.             _settextposition( w -> scr_row, 1);
  83.             AVL_UPDATE_LINE();
  84.             }
  85.         w -> current_line = temp2;
  86.         old = _settextposition(w -> scr_row = old.row,w -> scr_col = old.col);
  87.         w -> txt_col = pos2;
  88.         w -> changed = 1;
  89.         AVL_UPDATE_LINE();
  90.         }
  91. }        
  92.  
  93. void AVL_JOIN_LEFT() /* Join current line with Previos */
  94. {
  95.     AVL_EDIT_WINDOW_PTR w;
  96.     AVL_LINE_PTR temp, temp2;
  97.     struct rccoord old;
  98.     int pos, pos2;
  99.     w = &avl_windows[avl_window];
  100.     if (w -> current_line -> previous != w -> head)  {
  101.         if ((strlen(w -> current_line -> line) + strlen(w -> current_line -> previous -> line)) >= AVL_MAX_LINEL)  {
  102.             AVL_ERROR("Lines are too long. Can't perform join!");
  103.             return;
  104.             }
  105.         old = _settextposition(w -> scr_row+1,w -> scr_col);
  106.         temp = w -> current_line;
  107.         w -> current_line = w -> current_line -> previous;
  108.         AVL_CURSOR_END();
  109.         pos2 = w -> txt_col;
  110.         strcat(w -> current_line -> line, temp -> line);
  111.         w -> current_line -> next = temp -> next;
  112.         temp -> next -> previous = w -> current_line;
  113.         AVL_MAKE_NUMBER();
  114.         free(temp);
  115.         if (w -> scr_row != 1)
  116.             AVL_DELETE_LINE();
  117.         pos = w -> scr_row;
  118.         temp = temp2 = w -> current_line;
  119.         while (++pos != (w -> r2 + 1) && temp -> next != w -> head)    {
  120.             temp = temp -> next;
  121.             }
  122.         if (pos == (w -> r2 + 1) && temp != w -> head)  {
  123.             w -> current_line = temp;
  124.             w -> scr_row = (w -> r2 - 1);
  125.             _settextposition( (w -> r2 - 1), 1);
  126.             AVL_UPDATE_LINE();
  127.             }
  128.         w -> current_line = temp2;
  129.         if (old.row > 1)
  130.             old = _settextposition(w -> scr_row = old.row - 1,w -> scr_col = old.col);
  131.         else
  132.             old = _settextposition(w -> scr_row = old.row,w -> scr_col = old.col);
  133.         w -> txt_col = pos2;
  134.         AVL_UPDATE_LINE();
  135.         w -> changed = 1;
  136.         }
  137. }        
  138.  
  139.  
  140. int AVL_OFFSET()
  141. {
  142.     AVL_EDIT_WINDOW_PTR w;
  143.     int n, i, off = 0;
  144.     w = &avl_windows[avl_window];
  145.     n = AVL_COL();
  146.     off = 0;
  147.     for(i = (w -> c2 - w -> c1 + 1); i < n; i += 20)
  148.         off += 20;
  149.     return ( off );
  150. }
  151.  
  152. int AVL_COUNT()
  153. {
  154.     int i = 0;
  155.     AVL_EDIT_WINDOW_PTR w;
  156.     w = &avl_windows[avl_window];
  157.     avl_line_temp = w -> current_line;
  158.     for (; avl_line_temp != w -> head 
  159.            && i < w -> r2; avl_line_temp = avl_line_temp -> next)
  160.         ++i;
  161.     avl_line_temp = avl_line_temp -> previous;
  162.     return i;
  163. }
  164.  
  165. void AVL_OPEN_LINE()
  166. {
  167.    short left, top, right, bottom;
  168.    struct rccoord rc;
  169.  
  170.    _gettextwindow( &top, &left, &bottom, &right );
  171.    rc = _gettextposition();
  172.    _settextwindow( rc.row+1, left, bottom, right );
  173.    _scrolltextwindow( _GSCROLLDOWN );
  174.    _settextwindow( top, left, bottom, right );
  175.    _settextposition( rc.row+1, rc.col );
  176. }
  177.  
  178. void AVL_EDIT_ENTER()
  179. {
  180.     AVL_EDIT_WINDOW_PTR w;
  181.     AVL_LINE_PTR temp;
  182.     struct rccoord old;
  183.     short i, j, k;
  184.     old = _gettextposition();
  185.     w = &avl_windows[avl_window];
  186.     for(i = 0, j = 0; w -> current_line -> line [i] == ' '; ++i);
  187.     j = i;
  188.     temp = calloc(1,sizeof(AVL_LINE_SIZE));
  189.     temp -> previous = w -> current_line;
  190.     temp -> next     = w -> current_line -> next;
  191.     w -> current_line -> next -> previous = temp;
  192.     w -> current_line -> next = temp;
  193.     strcpy(temp -> line, w -> current_line -> line + w -> txt_col);
  194.     w -> current_line -> line [w -> txt_col] = '\0';
  195.     AVL_MAKE_NUMBER();
  196.     w -> txt_col = 0;
  197.     AVL_OPEN_LINE();
  198.     _settextposition(w -> scr_row,w -> scr_col = 1);
  199.     AVL_UPDATE_LINE();
  200.     if (w -> scr_row == (w -> r2 - w -> r1 + 1)) 
  201.         _scrolltextwindow( 1 );
  202.     else
  203.         w -> scr_row += 1;
  204.     w -> current_line = temp; 
  205.     w -> changed = 1;
  206.     if (strlen(temp -> line) > 0)
  207.         j = 0;  
  208.     for(i = 0; i < j; ++i)
  209.         w -> current_line -> line[i] = ' ';
  210.     if (j > 0)
  211.         w -> current_line -> line[i] = '\0';
  212.     _settextposition(w -> scr_row,w -> scr_col = (j < 78) ? j + 1 : 1);
  213.     w -> txt_col = (j < 78) ? j : 0;
  214.     AVL_UPDATE_LINE();
  215.     if (w -> offset != 0)  {
  216.         w -> offset = 0;
  217.         AVL_SCROLL();
  218.         }
  219. }
  220.  
  221. void AVL_SCROLL()
  222. {
  223.     AVL_EDIT_WINDOW_PTR w;
  224.     AVL_LINE_PTR temp;
  225.     struct rccoord old;
  226.     short i, j, k;
  227.     AVL_WIN_PTR t, t2;
  228.     w = &avl_windows[avl_window];
  229.     old = _gettextposition();
  230.     temp = w -> current_line;
  231.     j = old.row;
  232. /*
  233.     if ((w -> txt_col == strlen(temp -> line)) && (w -> txt_col > 0))
  234.         w -> txt_col -= 1;
  235. */
  236.     k = w -> txt_col;
  237.     for(i = j; i > 1; --i)  {
  238.         w -> current_line = w -> current_line -> previous;
  239.         }
  240.     w -> scr_row = 1;
  241.     avl_hscroll_on = 1;
  242.     _settextposition(1,1);
  243.     AVL_UPDATE_SCREEN();
  244.     _settextposition(old.row,old.col);
  245.     w -> current_line = temp;
  246.     w -> scr_row = j;
  247.     w -> scr_col = old.col;
  248.     w -> txt_col = k;
  249.     avl_hscroll_on = 0;
  250.     AVL_UPDATE_CURSOR();
  251. }
  252.  
  253.  
  254.  
  255. void AVL_UPDATE_STATUS_LINE()
  256. {
  257.     AVL_EDIT_WINDOW_PTR w;
  258.     char status[10];
  259.     char line[181];
  260.     char fn[121];
  261.     short att, attold;
  262.     short i, n;
  263.     char *p;
  264.     w = &avl_windows[avl_window];
  265.     attold = _gettextcursor();
  266.     if (w -> no_status == 'N') return;
  267.     if (avl_window < AVL_MAX_WINDOWS)
  268.         switch (tolower(w -> edit_mode))  {
  269.             case 'x' : strcpy(status,"Ovr"); att = 0x0007; break;
  270.             case 'i' : strcpy(status,"Ins"); att = 0x0707; break;
  271.             default  : w -> edit_mode = 'i'; strcpy(status,"Ins"); att = 0x0707; break;
  272.             }
  273.     else
  274.         strcpy(status,"Hlp");
  275.     AVL_MAKE_FN(fn, w -> file_name);
  276.     sprintf(line,"Line %3d Col %2d %-35s %s %-12s F1-Help             "
  277.         ,  w -> current_line -> line_no - 1
  278.         , w -> txt_col + 1
  279.         , avl_message
  280.         , status
  281.         , fn
  282.         );
  283.     n = strlen(line);
  284.     if (n > 80) n = 80;
  285.     p = line;
  286.     for(i = 1; i <= n; ++i, ++p)
  287. /*        AVL_PUT(*p,w -> r1 - 1,i,avl_sta_bk_color,avl_sta_color);   */
  288.         AVL_WVIDEO(*p,(unsigned char) (avl_sta_bk_color << 4 | avl_sta_color)
  289.             , AVL_MAP(w -> r1 - 1,i));
  290.     if (attold != att)
  291.         _settextcursor(att);    
  292. }
  293.  
  294.  
  295. void AVL_INIT_WINDOW(AVL_EDIT_WINDOW_PTR w, AVL_LINE_PTR first)
  296. {
  297.     short att;
  298.     att = _settextcursor(0x0607);
  299.     avl_find_txt[0] = '\0';
  300.     avl_replace_txt[0] = '\0';
  301.     avl_block_first_line = NULL;
  302.     avl_block_last_line = NULL;
  303.     avl_block_first_col = 0;
  304.     avl_block_last_col = 0;
  305.     sprintf(avl_blank_line,"%80s"," ");
  306.     w -> head         = first -> previous;
  307.     w -> current_line = first;
  308.     w -> no_status = 'Y';
  309.     w -> r1     = 2;
  310.     w -> c1     = 1;
  311.     w -> r2     = 25;
  312.     w -> c2     = 80;
  313.     w -> offset = 0;
  314.     w -> edit_mode = 'i';
  315.     w -> tabsize   = avl_tab_size;
  316.     w -> scr_col   = 1;
  317.     w -> scr_row   = 1;
  318.     w -> txt_col   = 0;
  319.     w -> line_no = 0;
  320.     avl_message[0] = '\0';
  321.     _settextwindow(w -> r1, w -> c1, w -> r2, w -> c2);
  322.     _setbkcolor( avl_txt_bk_color );
  323.     _settextcolor( avl_txt_color );
  324. }
  325.  
  326. char *AVL_MAKE_TXT_LINE()
  327. {
  328.     char *d;
  329.     int i, j = 0, n, n2 = 0;
  330.     AVL_EDIT_WINDOW_PTR w;
  331.     char *t, *t2;
  332.     w = &avl_windows[avl_window];
  333.     t = w -> current_line -> line;
  334.     d = w -> expanded_line;
  335.     n = strlen(t);
  336.     for(i = 0; i < n; ++i)  {
  337.         if (*(t + i) == '\t')  {
  338.             for (n2= 0; !(((j + 1) % w -> tabsize) == 0); ++n2)
  339.                 d[j++] = ' ';
  340.             d[j++] = ' ';
  341.             }
  342.         else 
  343.             d[j++] = *(t + i);
  344.         }
  345.     d[j] = '\0';        
  346.     return d;
  347. }        
  348.  
  349. void AVL_UPDATE_LINE()
  350. {
  351.     short i, j, k;
  352.     char *d;
  353.     char *p;
  354.     AVL_EDIT_WINDOW_PTR w;
  355.     w = &avl_windows[avl_window];
  356.     d = AVL_MAKE_TXT_LINE();
  357.     j = strlen(d);
  358.     if (w -> txt_col > (k = strlen(d)))
  359.         w -> txt_col = k;
  360.     if (w -> txt_col < 0) 
  361.         w -> txt_col = 0;
  362.     if (j <= w -> offset)
  363.         j = 0;
  364.     else
  365.         j = j - w -> offset + 1;
  366.     k = w -> scr_row + w -> r1 - 1;
  367.     i = (j > (w -> c2 - w -> c1 + 1)) ? (w -> c2 - w -> c1 + 1) : j;
  368.     p = d + w -> offset;
  369.     for(j = 1; j <= i; ++j, ++p)
  370.         AVL_WVIDEO(*p,(unsigned char) (avl_txt_bk_color << 4 | avl_txt_color) 
  371.             , AVL_MAP(k,j));
  372. /*        AVL_PUT(*p,k,j,avl_txt_bk_color,avl_txt_color);   */
  373.     for(; j <= (w -> c2 - w -> c1 + 1); ++j)
  374.         AVL_WVIDEO(' ',(unsigned char) (avl_txt_bk_color << 4 | avl_txt_color), AVL_MAP(k,j));
  375. /*        AVL_PUT(' ',k,j,avl_txt_bk_color,avl_txt_color);  */
  376.     strcpy(w -> current_line -> line,d);
  377.     if (!avl_hscroll_on)
  378.         AVL_UPDATE_CURSOR();
  379. }
  380.  
  381.  
  382. void show_sit(char *s)
  383. {
  384.     struct rccoord old;
  385.     static short x = 0;
  386.     AVL_EDIT_WINDOW_PTR w;
  387.     int n, j;
  388.     char msg[200];
  389.     if (x >= 6) x = 0;
  390.     w = &avl_windows[avl_window];
  391.     n = strlen(w -> current_line -> line);
  392.     old = _gettextposition();
  393.     _settextposition(10+x++,1);
  394.     sprintf(msg,"%s offset=%d scr_col=%d txt_col=%d len=%d char=%c[%d]", s, 
  395.         w -> offset, w -> scr_col, w -> txt_col, n 
  396.         , w -> current_line -> line [w -> txt_col]
  397.         , w -> current_line -> line [w -> txt_col]);
  398.     _outtext(msg);
  399.     j = getch();
  400.     _settextposition(old.row,old.col);
  401. }
  402.  
  403. void AVL_EDIT_INSERT(int ch)
  404. {
  405.     AVL_EDIT_WINDOW_PTR w;
  406.     short n, j, oldoffset;
  407.     char *p;
  408.     w = &avl_windows[avl_window];
  409.     oldoffset = w -> offset;
  410.     n = strlen(w -> current_line -> line);
  411. /*    if (w -> txt_col >= n)  
  412.         AVL_CURSOR_END();
  413. */
  414.     if (n >= AVL_MAX_LINEL) { putchar(7); return; }
  415.     if (w -> edit_mode == 'i') {   /*  Insert mode */
  416.         if ((n + 1) >= AVL_MAX_LINEL) { putchar(7); return; }
  417.         for (j = n; j >= w -> txt_col; --j)
  418.             w -> current_line -> line[j + 1] = w -> current_line -> line[j];
  419.         w -> current_line -> line[w -> txt_col] = ch;
  420.         }
  421.     else {
  422.         w -> current_line -> line[w -> txt_col] = ch;
  423.         if (w -> txt_col >= n)  {
  424.             w -> current_line -> line[w -> txt_col+1] = '\0';
  425.             }
  426.         }
  427.     w -> txt_col += 1;
  428.     w -> offset = AVL_OFFSET();
  429.     if (w -> offset != oldoffset)  
  430.         AVL_SCROLL();
  431.     w -> buffer_size += 1;
  432.     w -> changed = 1;
  433.     n = strlen(w -> current_line -> line);
  434.     AVL_UPDATE_LINE();
  435.     j = strlen(w -> current_line -> line);
  436.     if (j != n)  {
  437.         w -> txt_col += (j - n);
  438.         AVL_UPDATE_CURSOR();
  439.         }
  440. /*show_sit("Depois ==> ");
  441. */
  442. }
  443.  
  444.     AVL_FLIP_MODE()
  445. {
  446.     AVL_EDIT_WINDOW_PTR w;
  447.     w = &avl_windows[avl_window];
  448.     switch (tolower(w -> edit_mode))  {
  449.         case 'c' : w -> edit_mode = 'i';  break;
  450.         case 'i' : w -> edit_mode = 'x';  break;
  451.         case 'x' : w -> edit_mode = 'i';  break;
  452.         default  : AVL_ERROR("Invalid status mode..."); exit(1);
  453.         }
  454.     AVL_UPDATE_STATUS_LINE();
  455. }
  456.  
  457. void AVL_HOT_KEYS()
  458. {
  459.     AVL_WIN_PTR win;
  460.     win = AVL_MAKE_WINDOW(" Hot Keys ",4,3,17,76,avl_wnd_bk_color,avl_wnd_color);
  461.     /*          1         2         3         4         5         6         7 */
  462.     /* 1234567890123456789012345678901234567890123456789012345678901234567890 */
  463.     /* 
  464.  
  465.          Alternate keys: File Edit Compile Bind Run Window Options Ada Help
  466.                          F4 quit
  467.  
  468.                          Example: Alt-F ==> activates the File Menu
  469.  
  470.          Editing keys:   F5      goto line        Ctrl-G  delete char
  471.                          Ctrl-KB begin block      Ctrl-Y  delete line      
  472.                          Ctrl-KK end block        Ctrl-QR go begin text
  473.                          Ctrl-KC copy block       Ctrl-RC go end text
  474.                          Ctrl-KS save             Ins     insert/over. mode
  475.             
  476.     */
  477.     _settextcolor(avl_men_letter);
  478.     _settextposition(2,3);  _outtext("Alternate keys: ");
  479.     _settextcolor(avl_men_ready); _outtext("F");
  480.     _settextcolor(avl_men_letter); _outtext("ile ");
  481.     _settextcolor(avl_men_ready); _outtext("E");
  482.     _settextcolor(avl_men_letter); _outtext("dit ");
  483.     _settextcolor(avl_men_ready); _outtext("C");
  484.     _settextcolor(avl_men_letter); _outtext("ompile ");
  485.     _settextcolor(avl_men_ready); _outtext("B");
  486.     _settextcolor(avl_men_letter); _outtext("ind ");
  487.     _settextcolor(avl_men_ready); _outtext("R");
  488.     _settextcolor(avl_men_letter); _outtext("un ");
  489.     _settextcolor(avl_men_ready); _outtext("W");
  490.     _settextcolor(avl_men_letter); _outtext("indow ");
  491.     _settextcolor(avl_men_ready); _outtext("O");
  492.     _settextcolor(avl_men_letter); _outtext("ptions ");
  493.     _settextcolor(avl_men_ready); _outtext("A");
  494.     _settextcolor(avl_men_letter); _outtext("da ");
  495.     _settextcolor(avl_men_ready); _outtext("H");
  496.     _settextcolor(avl_men_letter); _outtext("elp");
  497.     _settextposition(3,19); _settextcolor(avl_men_ready); _outtext("F4");
  498.      _settextcolor(avl_men_letter); _outtext(" quit");
  499.     _settextposition(5,19); _outtext("Example: ");
  500.     _settextcolor(avl_men_ready); _outtext("Alt-F");
  501.     _settextcolor(avl_men_letter); _outtext(" ==> activates the File Menu");
  502.     _settextposition(7,3);  _outtext("Editing keys:   ");
  503.     _settextcolor(avl_men_ready); _outtext("F5");
  504.     _settextcolor(avl_men_letter); _outtext("      goto line        ");
  505.     _settextcolor(avl_men_ready); _outtext("Ctrl-G");
  506.     _settextcolor(avl_men_letter); _outtext("  delete char");
  507.     _settextposition(8,19); _settextcolor(avl_men_ready); _outtext("Ctrl-KB");
  508.     _settextcolor(avl_men_letter); _outtext(" begin block      ");
  509.     _settextcolor(avl_men_ready); _outtext("Ctrl-Y");
  510.     _settextcolor(avl_men_letter); _outtext("  delete line");
  511.     _settextposition(9,19); _settextcolor(avl_men_ready); _outtext("Ctrl-KK");
  512.     _settextcolor(avl_men_letter); _outtext(" end block        ");
  513.     _settextcolor(avl_men_ready); _outtext("Ctrl-QR");
  514.     _settextcolor(avl_men_letter); _outtext(" go begin text");
  515.     _settextposition(10,19); _settextcolor(avl_men_ready); _outtext("Ctrl-KC");
  516.     _settextcolor(avl_men_letter); _outtext(" copy block       ");
  517.     _settextcolor(avl_men_ready); _outtext("Ctrl-RC");
  518.     _settextcolor(avl_men_letter); _outtext(" go end text");
  519.     _settextposition(11,19);_settextcolor(avl_men_ready);  _outtext("Ctrl-KS");
  520.     _settextcolor(avl_men_letter); _outtext(" save             ");
  521.     _settextcolor(avl_men_ready); _outtext("Ins");
  522.     _settextcolor(avl_men_letter); _outtext("     insert/over. mode");
  523.     AVL_PAUSE(20);
  524.     AVL_DEL_WINDOW(win);
  525. }
  526.  
  527.  
  528. void AVL_WORD_BACKWARD()
  529. {
  530.     AVL_EDIT_WINDOW_PTR w;
  531.     char *p, *q;
  532.     w = &avl_windows[avl_window];
  533.     p = &( w -> current_line -> line[w -> txt_col] );
  534.     q = &( w -> current_line -> line[0] );
  535.     while (!(p == q || *p == ' ')) {  /* skip letters going left */
  536.         AVL_CURSOR_LEFT(1);           /* getting out of current word */
  537.         --p;
  538.         }
  539.     if (*p == ' ' && p != q) /* is there a blank? */
  540.         do { /* skip blanks */
  541.             AVL_CURSOR_LEFT(1); 
  542.             --p;
  543.             } while (*p == ' ' && p != q);
  544.     if (p != q)  { /* are we at the right of a symbol? */
  545.         while (!(p == q || *p == ' ')) {
  546.             AVL_CURSOR_LEFT(1); 
  547.             --p;
  548.             }
  549. /*        if (p != q)  {
  550.             AVL_CURSOR_RIGHT(1);   
  551.             ++p;
  552.             }
  553. */
  554.           }
  555.     if (*p == ' ')  
  556.         do {
  557.             AVL_CURSOR_RIGHT(1);   
  558.             ++p;
  559.             } while (*p == ' ');
  560. }
  561.  
  562. void AVL_WORD_FORWARD()
  563. {
  564.     AVL_EDIT_WINDOW_PTR w;
  565.     char *p;
  566.     w = &avl_windows[avl_window];
  567.     p = &( w -> current_line -> line[w -> txt_col] );
  568.     while (!(*p == '\0' || *p == ' ')) {
  569.         AVL_CURSOR_RIGHT(1); 
  570.         ++p;
  571.         }
  572.     if (*p == ' ') 
  573.         do {
  574.             AVL_CURSOR_RIGHT(1); 
  575.             ++p;
  576.             } while (*p == ' ');
  577. }    
  578.         
  579. void AVL_DO_HELP_INDEX(char *s, short pos)
  580. {
  581.     short i, k;
  582.     short nopt = 0;
  583.     char word[200];
  584.     char do_call[300];
  585.     char c;
  586.     char *opts[17];
  587.     c = *(s+pos);
  588.     if (!(isalpha(c) || c == '_')) {
  589.         AVL_ERROR("Activate the Search Help (F8) when the cursor is over a word");
  590.         return;
  591.         }
  592.     i = pos;
  593.     while (i >=0 && (isalpha(*(s+i)) || *(s+i) == '_')) --i;
  594.     if (i < 0) i = 0;
  595.     else ++i;
  596.     k = 0;
  597.     while (isalpha(*(s+i)) || *(s+i) == '_') word[k++] = *(s+i++);
  598.     word[k] = '\0';
  599.     opts[nopt++] = "Adahelp";
  600.     opts[nopt++] = word;
  601.     opts[nopt++] = NULL;
  602.     sprintf(do_call,"ADAHELP %s",word);
  603.     system(do_call);
  604. /*
  605.     if (AVL_EX_UNIT("ADAHELP", opts))  ;
  606. */
  607. }
  608.  
  609. void AVL_EDIT(char mode)
  610. {
  611.     int ch, no = 1;
  612.     char c;
  613.     int updt = 1;
  614.     short r1, r2, c1, c2, i, j;
  615.     extern int avl_ctrl_c;
  616.     AVL_LINE_PTR saved;
  617.     AVL_EDIT_WINDOW_PTR w;
  618.     short old_bk_color, old_color;
  619.     short old_sta_bk_color, old_sta_color;
  620.     w = &avl_windows[avl_window];
  621.     w -> edit_mode = mode;
  622.     strcpy(avl_message,"Press ESC to activate top menu");
  623.     AVL_UPDATE_CURSOR();
  624.     AVL_UPDATE_STATUS_LINE();
  625.     old_color = avl_txt_color;
  626.     old_bk_color = avl_txt_bk_color;
  627.     old_sta_color = avl_sta_color;
  628.     old_sta_bk_color = avl_sta_bk_color;
  629.     while ( 1 )  {
  630.         w = &avl_windows[avl_window];
  631.         if (!((old_sta_bk_color == avl_sta_bk_color) && (old_sta_color == avl_sta_color))) {
  632.             for(j = 1; j <= 80; ++j)  {
  633.                 c = *AVL_MAP(1,j);
  634.                 AVL_WVIDEO(c,(unsigned char) (avl_sta_bk_color << 4 | avl_sta_color), AVL_MAP(1,j));
  635.                 }
  636.             old_sta_bk_color = avl_sta_bk_color;
  637.             old_sta_color = avl_sta_color;
  638.             }
  639.         if (!((old_bk_color == avl_txt_bk_color) && (old_color == avl_txt_color))) {
  640.             _gettextwindow(&r1,&c1,&r2,&c2);
  641.             for(i = r1; i <= r2; ++i)
  642.                 for(j = c1; j <= c2; ++j)  {
  643.                     c = *AVL_MAP(i,j);
  644.                     AVL_WVIDEO(c,(unsigned char) (avl_txt_bk_color << 4 | avl_txt_color), AVL_MAP(i,j));
  645.                     }
  646.             old_bk_color = avl_txt_bk_color;
  647.             old_color = avl_txt_color;
  648.             }
  649.  
  650.         if (avl_open_error_file)  {
  651.             AVL_ENVIRONMENT('F');
  652.             avl_open_error_file = 0;
  653.             continue;
  654.             }
  655.  
  656.         if (!kbhit()) {
  657.             if (updt)  {
  658.                 AVL_UPDATE_CURSOR();
  659.                 AVL_UPDATE_STATUS_LINE();
  660.                 updt = 0;
  661.                 }
  662.             continue;
  663.             }
  664.         updt = 1;
  665.         ch = getch();
  666.         switch( ch )  {
  667.             case  1  : /* Ctrl-Left == Ctrl-A */ AVL_WORD_BACKWARD(); break;
  668.             case  6  : /* Ctrl-Right == Ctrl-F */ AVL_WORD_FORWARD(); break;
  669.             case  4  : /* Ctrl-D == Right */  AVL_CURSOR_RIGHT(1); break;
  670.             case  8  : { /*  Backspace */  
  671.                 if (w -> txt_col > 0) {
  672.                     w -> txt_col -= 1;
  673.                     if (w -> offset != AVL_OFFSET()) {
  674.                         w -> offset = AVL_OFFSET();
  675.                         AVL_SCROLL();
  676.                         }
  677.                     AVL_EDIT_DEL_RIGHT(no); 
  678.                     no = 0; 
  679.                     }
  680.                 else {  /* Join with the previous line */
  681.                     w -> changed = 1;
  682.                     w -> offset = 0;
  683.                     AVL_JOIN_LEFT();
  684.                     }
  685.                 break;
  686.                 }
  687.             case  9  :  /*  Tab       */  AVL_EDIT_INSERT(ch); break;
  688.             case 14  :  /*  Ctrl-N */
  689.             case 13  :  /*  Enter     */  AVL_EDIT_ENTER(); break;
  690.             /*  Control keys */
  691.             case  7 : /* Delete current char - Ctrl G */
  692.                 AVL_EDIT_DEL_RIGHT(no); 
  693.                 no = 0; 
  694.                 break;
  695.             case 11 : /* Mark Block - Ctrl K */
  696.                 ch = toupper(getch());
  697.                 if (ch == 'B' || ch == 'K') {
  698.                     AVL_GUIDE_MBLOCK ();
  699.                     break;
  700.                     }
  701.                 else if (ch == 'C')  {
  702.                     AVL_PROCESS_COPY();
  703.                     break;
  704.                     }
  705.                 else if (ch == 'S')  {
  706.                     AVL_SAVE();
  707.                     break;
  708.                     }
  709.                 if (ch == 0) ch = getch();
  710.                 AVL_ERROR("Use only Ctrl-k b, Ctrl-k k, Ctrl-k c and Crtl-k s");
  711.                 break;
  712.             case 17 : /* Go to begin/end of text file  Ctrl-Q R or C or Y */
  713.                 avl_ctrl_c = 0;
  714.                 ch = toupper(getch());
  715.                 if (ch == 89 || ch == 25)   {  /* Got a Ctrl-Q Y */
  716.                     w -> current_line -> line [w -> txt_col] = '\0';
  717.                     AVL_UPDATE_LINE();
  718.                     break;
  719.                     }
  720.                 AVL_UPDATE_LINE();
  721.                 if (ch == 'C' || avl_ctrl_c) {
  722.                     if (w -> head -> previous != w -> head)
  723.                         AVL_DO_GOTO(w -> head -> previous -> line_no);
  724.                     break;
  725.                     }
  726.                 else if (ch == 'R' || ch == 18) {
  727.                     avl_ctrl_c = 0;
  728.                     if (w -> head -> next != w -> head)
  729.                         AVL_DO_GOTO(w -> head -> next -> line_no);
  730.                     break;
  731.                     }
  732.                 if (ch == 0) ch = getch();
  733.                 AVL_ERROR("Use only Ctrl-q r, Ctrl-q c or Ctrl-q y");
  734.                 break;
  735.             case 22 : /* Ctrl-V == Ins key */ AVL_FLIP_MODE(); break;
  736.             case 25 : /* Delete current line - Ctrl Y */
  737.                 AVL_EDIT_DEL_LINE(no); 
  738.                 no = 0; 
  739.                 break;
  740.             case 27  :  /*  ESC       */  
  741.                 if (avl_cur_menu == 7 && avl_window == AVL_MAX_WINDOWS) 
  742.                     return;
  743.                 else {
  744.                     if (do_not_realy_exit) {
  745.                         AVL_EXIT();
  746.                         return;
  747.                         }
  748.                     AVL_ENVIRONMENT(0); 
  749.                     AVL_UPDATE_CURSOR();
  750.                     AVL_UPDATE_STATUS_LINE();
  751.                     updt = 1;
  752.                     break;
  753.                     }
  754.  
  755.                 break;
  756.             case  0  : {
  757.                 ch = getch();
  758.                 switch( ch ) {
  759.                     /*  Alt keys  */
  760.                     case 33 : /* File */ AVL_ENVIRONMENT('F'); break;
  761.                     case 59 : /* F1 without alternate   */ AVL_HOT_KEYS(); break;
  762.                     case 60 : /* F2 without alternate */ AVL_ENVIRONMENT('F'); break;
  763.                     case 66 : /* F8 without alternate */ AVL_DO_HELP_INDEX(w -> current_line -> line,w -> txt_col); break;
  764.                     case 18 : /* Edit */ AVL_ENVIRONMENT('E'); break;
  765.                     case 46 : /* Comp */ AVL_ENVIRONMENT('C'); updt = 1; break;
  766.                     case 48 : /* Bind */ AVL_ENVIRONMENT('B'); break;
  767.                     case 19 : /* Run  */ AVL_ENVIRONMENT('R'); break;
  768.                     case 17 : /* Wind */ AVL_ENVIRONMENT('W'); updt = 1; break;
  769.                     case 24 : /* Opti */ AVL_ENVIRONMENT('O'); break;
  770.                     case 30 : /* Ada  */ AVL_ENVIRONMENT('A'); break;
  771.                     case 35 : /* Help */ AVL_ENVIRONMENT('H'); break;
  772.                     case 107: /* Alt-F4   */ AVL_EXIT(); return;
  773.                     case 63 : /* F5   */ AVL_GOTO(); break;    
  774.                     case 65 : /* F7 */ AVL_BODY(); break;
  775.                     case 68 : /* F10 */
  776.                         if (avl_cur_menu == 7 && avl_window == AVL_MAX_WINDOWS) 
  777.                             return;
  778.                         else {
  779.                             if (do_not_realy_exit) {
  780.                                 AVL_EXIT();
  781.                                 return;
  782.                                 }
  783.                             AVL_ENVIRONMENT(0); 
  784.                             AVL_UPDATE_CURSOR();
  785.                             AVL_UPDATE_STATUS_LINE();
  786.                             updt = 1;
  787.                             break;
  788.                             }
  789.  
  790.                     case 82 : /* Ins  */ AVL_FLIP_MODE(); break;
  791.                     case 83 : /* Del  */ AVL_EDIT_DEL_RIGHT(no); no = 0; break;
  792.                     case 71 : /* Home */ AVL_CURSOR_HOME(); break;
  793.                     case 79 : /* End  */ AVL_CURSOR_END(); break;
  794.                     case 73 : /* PgUp */ AVL_CURSOR_PGUP(); break;
  795.                     case 81 : /* PgDn */ AVL_CURSOR_PGDN(); break;
  796.                     case 75 : /* Left */ AVL_CURSOR_LEFT(no); no = 0; break;
  797.                     case 77 : /* Right*/ AVL_CURSOR_RIGHT(no); no = 0; break;
  798.                     case 72 : /* Up   */ AVL_CURSOR_UP  (no); no = 0; break;
  799.                     case 80 : /* Down */ AVL_CURSOR_DOWN(no); no = 0; break;
  800.                     case 85 : /* SHIFT+F2 == Ctrl-K S */ AVL_SAVE(); break;
  801.                     case 92 : /* Shift+F9 == Alt-F D */ AVL_DOS_CMD(); break;
  802.                     case 115 : /* Ctrl-Left == Ctrl-A */ AVL_WORD_BACKWARD(); break;
  803.                     case 116 : /* Ctrl-Right == Ctrl-F */ AVL_WORD_FORWARD(); break;
  804.                     case 117 : /* Ctrl-End */
  805.                         AVL_DO_GOTO(w -> head -> previous -> line_no);
  806.                         break;
  807.                     case 119 : /* Ctrl-Home */
  808.                         AVL_DO_GOTO(w -> head -> next -> line_no);
  809.                         break;
  810.                     default : putchar(7); break;
  811.                     }
  812.                 break;
  813.                 }
  814.             default : {
  815.                 if (ch >= 32 && ch <= 126)  /* ' ' && '~' */ 
  816.                     AVL_EDIT_INSERT(ch);
  817.                 else
  818.                     putchar(7);
  819.                 break;
  820.                 }               
  821.             }
  822.         }
  823. }
  824.